﻿using Admin.Core.Common.Auth;
using Admin.Core.Common.Input;
using Admin.Core.Common.Output;
using Admin.Core.Common.ParamInput;
using Admin.Core.Model.Warehouse;
using Admin.Core.Repository.Warehouse.StockIn;
using Admin.Core.Repository.Warehouse.XbcLocation;
using Admin.Core.Repository.Warehouse.XbcMeterrial;
using Admin.Core.Repository.Warehouse.XbcTypeR;
using Admin.Core.Repository.Warehouse.XbcWarehouse;
using Admin.Core.Service.Warehouse.StockList.Output;
using Admin.Core.Service.Warehouse.XbcMeterrial.Input;
using Admin.Core.Service.Warehouse.XbcMeterrial.Output;
using AutoMapper;
using System;
using System.Collections.Generic;
using System.Text;
using System.Threading.Tasks;

namespace Admin.Core.Service.Warehouse.XbcMeterrial
{
    public class XbcMaterrialService : IXbcMaterrialService
    {

        private readonly IUser _user;
        private readonly IMapper _mapper;
        private readonly IXbcMaterrialRepository _xbcMaterrialRepository;
        private readonly IXbcWarehouseRepository _xbcWarehouseRepository;
        private readonly IXbcLocationRepository _xbcLocationRepository;
        private readonly IXbcTypeRepository _xbcTypeRepository;
        private readonly IStockInRepository _stockInRepository;
        public XbcMaterrialService(IUser user, IMapper mapper
            , IXbcMaterrialRepository xbcMaterrialRepository
            , IXbcTypeRepository xbcTypeRepository
            , IXbcWarehouseRepository xbcWarehouseRepository
            , IStockInRepository stockInRepository
            , IXbcLocationRepository xbcLocationRepository)
        {
            _user = user;
            _mapper = mapper;
            _xbcTypeRepository = xbcTypeRepository;
            _stockInRepository = stockInRepository;
            _xbcWarehouseRepository = xbcWarehouseRepository;
            _xbcLocationRepository = xbcLocationRepository;
            _xbcMaterrialRepository = xbcMaterrialRepository;
        }

        /// <summary>
        /// 获取物料信息
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public async Task<IResponseOutput> GetAsync(long id)
        {
            var result = await _xbcMaterrialRepository.GetAsync<XbcMaterrialGetOutput>(id);
            _stockInRepository.baseRepository.Where(x => x.XbcMatterrialId == id && x.Num > 0).Count(out var total);
            result.CanChangeType = total > 0;
            return ResponseOutput.Ok(result);
        }

        /// <summary>
        /// 获取物料信息
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public async Task<IResponseOutput> GetMaterDetailAsync(long id)
        {
            var result = await _xbcMaterrialRepository.baseRepository.Select.Where(x => x.Id.Equals(id)).Count(out var total).ToOneAsync(a => new
            {
                Wlms = a.Name,
                Wlgg = a.Wlgg,
                CustomerCode =  a.Khdm.Name,
                Dw = a.Ckdw.Name,
                XbcLocationId = a.XbcLocationId
            });
            if (total == 0)
            {
                return ResponseOutput.NotOk("料号异常！");
            }
            return ResponseOutput.Ok(result);
        }

        //public async Task<IResponseOutput> PageAsync(PageInput<XbcMaterrialFilterInput> input)
        //{
        //    var key = input.Filter?.Name;
        //    var typeId = input.Filter?.XbcTypeId;
        //    var list = await _xbcMaterrialRepository.baseRepository.Select
        //    .WhereIf(key.NotNull(), a => a.Code.Contains(key))
        //    .WhereIf(typeId != null, a => a.XbcTypeId.Equals(typeId))
        //    .Count(out var total)
        //    .OrderByDescending(true, c => c.Id)
        //    .Page(input.CurrentPage, input.PageSize)
        //    .ToListAsync(a => new XbcMaterrialListOutput { TypeName = a.XbcType.Name, LocationName = a.XbcLocation.Name, ZxffdwName = a.Zxffdw.Name, ZxffslName = a.Zxffsl.Name, KhDm = a.Khdm.Name, CkdwName = a.Ckdw.Name });
        //    //var data = new PageOutput<XbcMaterrialListOutput>()
        //    //{
        //    //    List = list,
        //    //    Total = total
        //    //};
        //    var data = new VxePageOutPut<XbcMaterrialListOutput>()
        //    {
        //        Result = list,
        //        Page = new VxePage { currentPage = input.CurrentPage, pageSize = input.PageSize, total = total, totalResult = total }
        //    };
        //    return ResponseOutput.Ok(data);
        //}


        public async Task<List<XbcMaterrialListOutput>> GetAllPageAsync(string name ,long? xbcTypeId)
        {
            var list = await _xbcMaterrialRepository.baseRepository.Select
            .WhereIf(name.NotNull(), a => a.Code.Contains(name))
            .WhereIf(xbcTypeId != null, a => a.XbcTypeId.Equals(xbcTypeId))
            .OrderByDescending(true, c => c.Id)
            .ToListAsync(a => new XbcMaterrialListOutput { TypeName = a.XbcType.Name, LocationName = a.XbcLocation.Name, ZxffdwName = a.Zxffdw.Name, ZxffslName = a.Zxffsl.Name, KhDm = a.Khdm.Name, CkdwName = a.Ckdw.Name });
            return list;
        }


        public async Task<IResponseOutput> PageAsync(PageInput<XbcMaterrialFilterInput> input)
        {
            var key = input.Filter?.Name;
            var typeId = input.Filter?.XbcTypeId;
            var list = await _xbcMaterrialRepository.baseRepository.Select
            .WhereIf(key.NotNull(), a => a.Code.Contains(key))
            .WhereIf(typeId != null, a => a.XbcTypeId.Equals(typeId))
            .Count(out var total)
            .OrderByDescending(true, c => c.Id)
            .Page(input.CurrentPage, input.PageSize)
            .ToListAsync(a => new XbcMaterrialListOutput { TypeName = a.XbcType.Name, LocationName = a.XbcLocation.Name, ZxffdwName = a.Zxffdw.Name, ZxffslName = a.Zxffsl.Name, KhDm = a.Khdm.Name, CkdwName = a.Ckdw.Name });
            var data = new PageOutput<XbcMaterrialListOutput>()
            {
                List = list,
                Total = total
            };
            return ResponseOutput.Ok(data);
        }

        /// <summary>
        /// 根据物料类型获取料号
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public async Task<IResponseOutput> GetMaterListAsync(long id)
        {
            var ls = await _xbcMaterrialRepository.baseRepository.Select
                  .Where(a => a.Enabled == true && a.XbcTypeId == id)
                  .ToListAsync(a => new
                  {
                      Value = a.Id,
                      Label = a.Code
                  });

            return ResponseOutput.Ok(ls);
        }




        public async Task<IResponseOutput> AddAsync(XbcMaterrialAddInput input)
        {
            var entity = _mapper.Map<XbcMaterrialEntity>(input);
            entity.TenantId = _user.TenantId;
            var id = (await _xbcMaterrialRepository.baseRepository.InsertAsync(entity)).Id;
            return ResponseOutput.Result(id > 0);
        }

        public async Task<IResponseOutput> UpdateAsync(XbMaterrialUpdateInput input)
        {
            if (!(input?.Id > 0))
            {
                return ResponseOutput.NotOk();
            }
            if (input.Enabled == false)
            {
                _stockInRepository.baseRepository.Where(x => x.XbcMatterrialId == input.Id && x.Num > 0).Count(out var total);
                if (total > 0)
                {
                    return ResponseOutput.NotOk("该物料已存在有效库存，不可禁用！");
                }
            }
            var entity = await _xbcMaterrialRepository.GetAsync(input.Id);
            if (!(entity?.Id > 0))
            {
                return ResponseOutput.NotOk("库位不存在！");
            }
            _mapper.Map(input, entity);
            await _xbcMaterrialRepository.UpdateAsync(entity);
            return ResponseOutput.Ok();
        }

        public async Task<IResponseOutput> SoftDeleteAsync(long id)
        {
            _stockInRepository.baseRepository.Where(x => x.XbcMatterrialId == id).Count(out var total);
            if (total > 0)
            {
                return ResponseOutput.NotOk("该物料已存在库存数据记录，不可删除！");
            }
            var result = await _xbcMaterrialRepository.SoftDeleteAsync(id);
            return ResponseOutput.Result(result);
        }

        public async Task<IResponseOutput> BatchSoftDeleteAsync(long[] ids)
        {
            var result = await _xbcMaterrialRepository.SoftDeleteAsync(ids);
            return ResponseOutput.Result(result);
        }

    }
}
